package com.aisile.admin.service.impl;

import cn.hutool.core.util.IdUtil;
import com.aisile.admin.feign.ArticleFeign;
import com.aisile.admin.feign.WemediaFeign;
import com.aisile.admin.mapper.AdChannelMapper;
import com.aisile.admin.mapper.AdSensitiveMapper;
import com.aisile.admin.service.WemediaNewsAutoScanService;
import com.aisile.common.aliyun.scan.GreenImagesForUrlScan;
import com.aisile.common.aliyun.scan.GreenTextForContentScan;
import com.aisile.common.exception.CustomExceptionCatch;
import com.aisile.common.exception.ExceptionCatch;
import com.aisile.model.admin.dtos.NewsAuthDto;
import com.aisile.model.admin.pojos.AdChannel;
import com.aisile.model.admin.pojos.AdSensitive;
import com.aisile.model.article.pojos.ApArticle;
import com.aisile.model.article.pojos.ApArticleConfig;
import com.aisile.model.article.pojos.ApArticleContent;
import com.aisile.model.article.pojos.ApAuthor;
import com.aisile.model.common.dtos.ResponseResult;
import com.aisile.model.common.enums.AppHttpCodeEnum;
import com.aisile.model.common.enums.WemediaHttpCodeEnum;
import com.aisile.model.media.pojos.WmNews;
import com.aisile.utils.common.SensitiveWordUtil;
import com.aisile.utils.common.SnowflakeIdWorker;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @Auther:yry
 * @Date:2024/1/9 0009
 * @VERSON:1.0
 */
@Service
@SuppressWarnings("ALL")
public class WemediaNewsAutoScanServiceImpl implements WemediaNewsAutoScanService {

    @Autowired
    private WemediaFeign wemediaFeign;

    @Autowired
    private ArticleFeign articleFeign;

    @Autowired
    private AdChannelMapper adChannelMapper;

//    @Autowired // 只根据type
//    @Qualifier // 只根据名字
//    //spring 推荐Resource
//    @Resource // 先根据byname  bytype

    @Autowired
    private AdSensitiveMapper adSensitiveMapper;

    @Autowired
    private GreenTextForContentScan greenTextForContentScan;

    @Autowired
    private GreenImagesForUrlScan greenImagesForUrlScan;

    @Override
    public void autoScanByWemediaNewsId(Integer id) {
        // 文章id  查询文章
        if (id == null) {
            CustomExceptionCatch.catchWemedia(WemediaHttpCodeEnum.DATA_NOT_EXIST);
        }
        // 远程调用获取 wemediaNews数据
        WmNews wmNews = wemediaFeign.findByIdToFeign(id);
        if (wmNews == null) {
            CustomExceptionCatch.catchWemedia(WemediaHttpCodeEnum.DATA_NOT_EXIST);
        }
        // 开始实现业务逻辑
        if (wmNews.getStatus().equals((short) 4)) {
            // 不用申了  直接发布
            // 直接修改状态 = 9
            this.saveAppArticleInfo(wmNews);
            return;
        }
        if (wmNews.getPublishTime() != null) {
            if (wmNews.getStatus().equals((short) 8) && (wmNews.getPublishTime().getTime() <= System.currentTimeMillis())) {
                //直接修改状态 = 9
                this.saveAppArticleInfo(wmNews);
                return;
            }
        }

        // 状态 = 1  调用敏感词管理  文本反垃圾检查  图片审核
        if (wmNews.getStatus().equals((short) 1)) {
            // 先获取待审核的文字  和  图片
            Map<String, List<String>> textAndImagesMap = this.getTextAndImages(wmNews);
            List<String> texts = textAndImagesMap.get("texts");
            List<String> images = textAndImagesMap.get("images");
            // 先查询敏感词
            if (!checkTextAsSensitive(texts, wmNews)) {
                return;
            }
            if (!checkTextAsAliyun(texts, wmNews)) {
                return;
            }
            if (!checkImagesAsAliyun(texts, wmNews)) {
                return;
            }
            // 没有任何毛病，然后看发布时间
            if(wmNews.getPublishTime()!=null){
                if((wmNews.getPublishTime().getTime()>= System.currentTimeMillis()) && (!wmNews.getStatus().equals((short)3))){
                    this.updateWmnews(wmNews, (short)8, "文章审核成功，没有到指定发布时间，待发布");
                    // 直接发送RabbitMQ 延时或者死信
                    return;
                }
            }
            // 正常审核  = 9
            if(!wmNews.getStatus().equals((short)3)){
                this.saveAppArticleInfo(wmNews);
            }
        }
    }

    @Override
    public ResponseResult updateStatus(Integer type, NewsAuthDto dto) {
        //1.参数检查
        if(dto == null || dto.getId() == null){
            CustomExceptionCatch.catchWemedia(WemediaHttpCodeEnum.DATA_NOT_EXIST);
        }
        if(type<0 || type>1){
            CustomExceptionCatch.catchWemedia(WemediaHttpCodeEnum.DATA_NOT_EXIST);
        }
        // 远程调用获取 wemediaNews数据
        WmNews wmNews = wemediaFeign.findByIdToFeign(dto.getId());
        if(wmNews == null){
            CustomExceptionCatch.catchWemedia(WemediaHttpCodeEnum.DATA_NOT_EXIST);
        }
        if(type == 0){
            updateWmnews(wmNews,(short)2,dto.getMsg());
        }else{
            //4.人工审核通过
            updateWmnews(wmNews,(short)4,"人工审核通过");
            autoScanByWemediaNewsId(dto.getId());
        }
        return ResponseResult.okResult(WemediaHttpCodeEnum.SUCCESS);
    }

    /**
     * 敏感词检查
     * 1. 检查  2。修改wmnews状态 stauts = 2
     *
     * @return
     */
    private boolean checkTextAsSensitive(List<String> texts, WmNews wmNews) {
        // 先构建 initMap  DFA算法
        List<AdSensitive> list = adSensitiveMapper.selectList(null);
        // 第一种
        List<String> words = new ArrayList<>();
        for (AdSensitive item : list) {
            words.add(item.getSensitives());
        }
        // 第二种
        List<String> words1 = list.stream().map(AdSensitive::getSensitives).collect(Collectors.toList());
        // 第三种
        List<String> words2 = adSensitiveMapper.findAllSensitive();

        SensitiveWordUtil.initMap(words2);
        // 把texts ==> 字符串
        StringBuilder sb = new StringBuilder();
        for (String text : texts) {
            sb.append(text);
        }
        Map<String, Integer> map = SensitiveWordUtil.matchWords(sb.toString());
        if (map.size() > 0) {
            this.updateWmnews(wmNews, (short) 2, "文章中出现平台禁用敏感词汇。");
            return false;
        }
        return true;

    }

    /**
     * 文本反垃圾检查
     * 1. 检查  2。修改wmnews状态 stauts = 2   stauts = 3
      * @param texts
     * @param wmNews
     * @return
     */
    private boolean checkTextAsAliyun(List<String> texts, WmNews wmNews){
        //Integer textScore =  greenTextForContentScan.textScan(texts);
        Integer textScore =  1;
        if(textScore >=0){
            if(textScore!=0){
                // 疑似
                this.updateWmnews(wmNews, (short)3, "文章文本出现垃圾词汇，需要人工审核");
            }
        }else{
            // 违规
            this.updateWmnews(wmNews, (short) 2, "文章中出现平台禁用敏感词汇。");
            return false;
        }
        return  true;
    }
    // 图片检查
    private boolean checkImagesAsAliyun(List<String> images, WmNews wmNews){
        //Integer textScore =  greenImagesForUrlScan.imagesScan(images);
        Integer textScore =  1;
        if(textScore >=0){
            if(textScore!=0){
                // 疑似
                this.updateWmnews(wmNews, (short)3, "文章文本出现违规图片，需要人工审核");
            }
        }else{
            // 违规
            this.updateWmnews(wmNews, (short) 2, "文章中出现平台禁用图片。");
            return false;
        }
        return  true;
    }


    /**
     * key   = text   images   value  List<文字、图片路径>
     * <p>
     * "[{"type":"text","value":"dfgfdg"},
     * {"type":"image","value":"http://192.168.200.130/group1/M00/00/00/wKjIgl5sNZqAISVbAAENauaC55A067.png"},
     * {"type":"image","value":"http://192.168.200.130/group1/M00/00/00/wKjIgl5sNYOAA2vyAACEiYuUHUc785.png"},
     * {"type":"text","value":"请输入文章内容..."}]
     * [] = List,数组                    {}  = Map(Pojo)
     * JSON  JSON.parseArray()           JSON.parseObject()
     * [{
     * "one" :{
     * "two" :"1"
     * }
     * }]
     * dto
     * 匿名类
     */
    private Map<String, List<String>> getTextAndImages(WmNews wmNews) {

        JSONArray jsonArray = new JSONArray();

        JSONObject jsonObject = new JSONObject();
        JSONObject jsonObjecttwo = new JSONObject();
        jsonObjecttwo.put("two", "1");
        jsonObject.put("one", jsonObjecttwo);

        jsonArray.add(jsonObject);
        System.out.println(jsonObject.toJSONString());
        System.out.println(jsonArray);
        System.out.println("============================================以上是测试使用");


        String str = wmNews.getContent();  // “[]”
        List<Map> contents = JSON.parseArray(str, Map.class);
        List<String> texts = new ArrayList<>();
        List<String> images = new ArrayList<>();
        contents.stream().forEach(x -> {
            if ("image".equals(x.get("type"))) {
                images.add((String) x.get("value"));
            }
            if ("text".equals(x.get("type"))) {
                texts.add((String) x.get("value"));
            }
        });
        // 标题
        if (wmNews.getTitle() != null) {
            texts.add(wmNews.getTitle());
        }
        // 封面图片
        if (wmNews.getImages() != null && wmNews.getType() != 0) {
            String[] strings = wmNews.getImages().split(",");
            images.addAll(Arrays.asList(strings));
        }
        // 封装map
        Map<String, List<String>> result = new HashMap<>();
        result.put("texts", texts);
        result.put("images", images);
        return result;
    }

    /**
     * 保存三个文章表信息  以及修改文章审核状态 status = 9
     */
    private void saveAppArticleInfo(WmNews wmNews) {
        // 保存文章基本信息
        ApArticle apArticle = this.saveAparticle(wmNews);
        // 保存文章配置信息
        this.saveApArticleConfig(apArticle);
        // 保存文章内容信息
        this.saveApArticleContent(apArticle, wmNews);
        // 反向维护下 发布库文章id
        wmNews.setArticleId(apArticle.getId());
        // 修改文章状态 审核成功  status = 9
        this.updateWmnews(wmNews, (short) 9, "审核成功，发布！");
    }

    /**
     * 公用的审核方法 status =  2   3   8 (成功、待发布)   9
     *
     * @param wmNews
     * @param status
     * @param msg
     */
    private void updateWmnews(WmNews wmNews, Short status, String msg) {
        if (msg != null) {
            // 失败的拒绝原因
            wmNews.setReason(msg);
        }
        wmNews.setStatus(status);
        wemediaFeign.updateWmNewsForFeign(wmNews);
    }

    /**
     * 保存文章配置信息
     *
     * @param apArticle
     */
    private void saveApArticleConfig(ApArticle apArticle) {
        ApArticleConfig apArticleConfig = new ApArticleConfig();
        apArticleConfig.setId(IdUtil.getSnowflakeNextId());
        apArticleConfig.setArticleId(apArticle.getId());
        apArticleConfig.setIsDown(false);
        apArticleConfig.setIsDelete(false);
        apArticleConfig.setIsForward(true);
        apArticleConfig.setIsComment(true);
        articleFeign.saveApArticleConfig(apArticleConfig);
    }

    /**
     * 保存文章内容信息
     *
     * @param apArticle
     * @param wmNews
     */
    private void saveApArticleContent(ApArticle apArticle, WmNews wmNews) {
        ApArticleContent apArticleContent = new ApArticleContent();
        apArticleContent.setContent(wmNews.getContent());
        apArticleContent.setArticleId(apArticle.getId());
        apArticleContent.setId(IdUtil.getSnowflakeNextId());
        articleFeign.saveApArticleContent(apArticleContent);
    }

    /**
     * 保存文章基本信息
     *
     * @param wmNews
     * @return
     */
    private ApArticle saveAparticle(WmNews wmNews) {
        SnowflakeIdWorker snowflakeIdWorker = new SnowflakeIdWorker(1, 1);
        ApArticle apArticle = new ApArticle();
        // 自维护ID
        apArticle.setId(snowflakeIdWorker.nextId());
        apArticle.setTitle(wmNews.getTitle()); // 标题
        apArticle.setChannelId(wmNews.getChannelId()); // 频道id
        apArticle.setLayout(wmNews.getType());
        apArticle.setFlag((byte) 0);
        apArticle.setImages(wmNews.getImages());
        apArticle.setLabels(wmNews.getLabels());
        apArticle.setLikes(0);
        apArticle.setCollection(0);
        apArticle.setComment(0);
        apArticle.setViews(0);
        apArticle.setCreatedTime(new Date());
        apArticle.setPublishTime(new Date());
        // 作者   频道
        AdChannel adChannel = adChannelMapper.selectById(apArticle.getChannelId());
        if (adChannel == null) {
            apArticle.setChannelName("其他");
        } else {
            apArticle.setChannelName(adChannel.getName());
        }
        // 作者
        ApAuthor apAuthor = articleFeign.findByWmUserId(wmNews.getUserId());
        if (apAuthor == null) {
            apArticle.setAuthorId(0L);
            apArticle.setAuthorName("匿名");
        } else {
            apArticle.setAuthorId(apAuthor.getId().longValue());
            apArticle.setAuthorName(apAuthor.getName());
        }
        return articleFeign.saveArticle(apArticle);
    }

}
